package com.haoran.dwz.web;

import java.util.ArrayList;
import java.util.List;

import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.domain.Sort;
import org.springframework.data.domain.Sort.Direction;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;

import com.haoran.dwz.common.util.EmailUtil;
import com.haoran.dwz.common.validator.ValidatorUtil;
import com.haoran.dwz.common.validator.group.AddGroup;
import com.haoran.dwz.domain.entities.PaginationEntity;
import com.haoran.dwz.domain.entities.User;
import com.haoran.dwz.rest.R;
import com.haoran.dwz.rest.ReturnCode;
import com.haoran.dwz.service.AuthService;
import com.haoran.dwz.service.UserService;
import com.haoran.dwz.wrapper.PaginationWrapper;

import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;

@Api(tags = { "User" }, description = "用户管理", position = 1)
@Controller
@RequestMapping(value = "/user")
public class UserController {

	private Logger logger = LoggerFactory.getLogger(getClass());

	@Autowired
	private UserService userService;
	
	
	@Autowired
	private AuthService authService;

	@ApiOperation("初始化系统")
	@RequestMapping(path = "initialization", method = RequestMethod.POST)
	@ResponseBody
	public R cleanAndInit(@ApiParam(name = "password", value = "root密码") @RequestParam String password,
			@ApiParam(name = "newPwd", value = "初始化后root密码") @RequestParam String newPwd) {
		try {
			logger.info("initialization system root");
			return R.success(userService.cleanAndInit(password, newPwd));
		} catch (Exception e) {
			return R.failure(e);
		}
	}

	@ApiOperation("分页查询所有的用户信息")
	@RequestMapping(value = "page-list", method = { RequestMethod.GET })
	@ResponseBody
	public PaginationWrapper findByPageable(UserVO userVO) {
		Sort sort;
		if (StringUtils.isNotBlank(userVO.getSidx()) && StringUtils.isNotBlank(userVO.getOrder())) {
			sort = new Sort(userVO.getDirection(), userVO.getSidx());
		} else {
			sort = new Sort(Direction.ASC, "username");
		}
		Pageable pageable = new PageRequest(userVO.getPage() - 1, userVO.getLimit(), sort);
		User user = new User();
		user.setUsername(userVO.getUsername());
		Page<User> entryByPageable = userService.findByPageable(user, pageable);
		
		//User 的信息太多 
		List<UserVO> list = new ArrayList<>();
		for (User user2 : entryByPageable) {
			list.add(new UserVO(user2.getId(),user2.getUsername(), user2.getEmail(), user2.isEnabled(), user2.getDefaultRole().getName()));
		}
		PaginationWrapper pageUtil = new PaginationWrapper(list, entryByPageable.getTotalElements(), userVO.getLimit(), userVO.getPage());
		return pageUtil;
	}

	@ApiOperation("查询所有用户列表")
	@RequestMapping(method = RequestMethod.GET)
	@ResponseBody
	public R list() {
		try {
			return R.success(userService.listAll());
		} catch (Exception e) {
			return R.failure(e);
		}
	}

	@ApiOperation(value = "新增用户")
	@RequestMapping(value = "/save", method = RequestMethod.POST)
	@ResponseBody
	public R newAdd(@ApiParam("新增用户")@RequestBody com.haoran.dwz.domain.pojo.UserVO addedUser) {
		try {
			ValidatorUtil.validateEntity(addedUser, AddGroup.class);
			if(!StringUtils.equals(addedUser.getPassword(), addedUser.getPwd())) {
				return R.result(ReturnCode.VALID_ERROR,"两次输入的密码不一致");
			}
			if(!EmailUtil.checkEmail(addedUser.getEmail())) {
				return R.result(ReturnCode.VALID_ERROR,"邮箱不正确");
			}
			User user = com.haoran.dwz.domain.pojo.UserVO.convert(addedUser);
			return authService.register(user, true);
		} catch (Exception e) {
			e.printStackTrace();
			return R.failure(e);
		}
	}
	
	@ApiOperation("批量删除用户")
	@RequestMapping(path = "bantchDel",method = RequestMethod.POST)
	@ResponseBody
	public R delete(
			@RequestParam(name = "usernames[]", required = true) @ApiParam(name = "usernames", value = "用户名", required = true) String[] usernames) {
		
		if (usernames == null || usernames.length == 0) {
			return R.success();
		} else {
			try {
				userService.deleteByUsername(usernames);
				return R.success();
			} catch (Exception e) {
				return R.failure(e);
			}
		}
		
	}
	
	@ApiOperation("删除用户")
	@RequestMapping(method = RequestMethod.DELETE)
	@ResponseBody
	public R delete(
			@RequestParam(name = "username", required = true) @ApiParam(name = "username", value = "用户名", required = true) String username) {
		try {
			if (StringUtils.isBlank(username)) {
				return R.result(ReturnCode.VALID_ERROR, "请输入用户名");
			}
			userService.deleteByUsername(username);
			return R.success();
		} catch (Exception e) {
			return R.failure(e);
		}
	}

	@ApiOperation("禁用用户")
	@RequestMapping(path = "disable", method = RequestMethod.POST)
	@ResponseBody
	public R disable(
			@RequestParam(name = "username", required = true) @ApiParam(name = "username", value = "用户名", required = true) String username) {
		try {
			if (StringUtils.isBlank(username)) {
				return R.result(ReturnCode.VALID_ERROR, "请输入用户名");
			}
			userService.disableByUsername(username);
			return R.success();
		} catch (Exception e) {
			return R.failure(e);
		}
	}

	@ApiOperation("启用用户")
	@RequestMapping(path = "enabled", method = RequestMethod.POST)
	@ResponseBody
	public R enabled(
			@RequestParam(name = "username", required = true) @ApiParam(name = "username", value = "用户名", required = true) String username) {
		try {
			if (StringUtils.isBlank(username)) {
				return R.result(ReturnCode.VALID_ERROR, "请输入用户名");
			}
			userService.enabledByUsername(username);
			return R.success();
		} catch (Exception e) {
			return R.failure(e);
		}
	}

	@ApiOperation("给用户分配角色")
	@RequestMapping(path = "grant", method = RequestMethod.POST)
	@ResponseBody
	public R grant(
			@RequestParam(name = "username", required = true) @ApiParam(name = "username", value = "用户名", required = true) String username,
			@RequestParam(name = "number", required = true) @ApiParam(name = "authority", value = "角色编码", required = true) String authority) {
		try {
			if (StringUtils.isBlank(username)) {
				return R.result(ReturnCode.VALID_ERROR, "请输入用户名");
			}
			if (StringUtils.isBlank(username)) {
				return R.result(ReturnCode.VALID_ERROR, "请输入角色编码");
			}
			userService.grantAuthorityByUsername(username, authority);
			return R.success();
		} catch (Exception e) {
			return R.failure(e);
		}
	}

	@ApiOperation("收回用户分配角色")
	@RequestMapping(path = "revoke-role", method = RequestMethod.POST)
	@ResponseBody
	public R revoke(
			@RequestParam(name = "username", required = true) @ApiParam(name = "username", value = "用户名", required = true) String username,
			@RequestParam(name = "number", required = true) @ApiParam(name = "number", value = "角色编码", required = true) String number) {
		try {
			if (StringUtils.isBlank(username)) {
				return R.result(ReturnCode.VALID_ERROR, "请输入用户名");
			}
			if (StringUtils.isBlank(username)) {
				return R.result(ReturnCode.VALID_ERROR, "请输入角色编码");
			}
			userService.revokeRoleByUsername(username, number);
			return R.success();
		} catch (Exception e) {
			return R.failure(e);
		}
	}

	@ApiOperation("给用户分配组")
	@RequestMapping(path = "group", method = RequestMethod.POST)
	@ResponseBody
	public R group(
			@RequestParam(name = "username", required = true) @ApiParam(name = "username", value = "用户名", required = true) String username,
			@RequestParam(name = "number", required = true) @ApiParam(name = "number", value = "分组编码", required = true) String number) {
		try {
			if (StringUtils.isBlank(username)) {
				return R.result(ReturnCode.VALID_ERROR, "请输入用户名");
			}
			if (StringUtils.isBlank(username)) {
				return R.result(ReturnCode.VALID_ERROR, "请输入分组编码");
			}
			userService.groupByUsername(username, number);
			return R.success();
		} catch (Exception e) {
			return R.failure(e);
		}
	}

	@ApiOperation("移除用户分组")
	@RequestMapping(path = "remove-group", method = RequestMethod.POST)
	@ResponseBody
	public R removeGroup(
			@RequestParam(name = "username", required = true) @ApiParam(name = "username", value = "用户名", required = true) String username,
			@RequestParam(name = "number", required = true) @ApiParam(name = "number", value = "分组编码", required = true) String number) {
		try {
			if (StringUtils.isBlank(username)) {
				return R.result(ReturnCode.VALID_ERROR, "请输入用户名");
			}
			if (StringUtils.isBlank(username)) {
				return R.result(ReturnCode.VALID_ERROR, "请输入分组编码");
			}
			userService.removeGroupByUsername(username, number);
			return R.success();
		} catch (Exception e) {
			return R.failure(e);
		}
	}

	@ApiOperation("用户密码修改")
	@RequestMapping(path = "change-pwd", method = RequestMethod.POST)
	@ResponseBody
	public R changePwd(
			@RequestParam(name = "oldpwd", required = true) @ApiParam(name = "oldpwd", value = "旧密码", required = true) String oldPwd,
			@RequestParam(name = "newpwd", required = true) @ApiParam(name = "newpwd", value = "新密码", required = true) String newPwd,
			@RequestParam(name = "validpwd", required = true) @ApiParam(name = "validpwd", value = "再次新密码", required = true) String validPwd) {
		try {
			if(!StringUtils.equals(newPwd, validPwd)) {
				return R.result(ReturnCode.VALID_ERROR,"两次输入的密码不一致");
			}
			Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
			Object principal = authentication.getPrincipal();
			if (principal != null && principal instanceof User) {
				User jwtUser = (User) principal;
				if (!jwtUser.isEnabled()) {
					R.result(ReturnCode.DISABLED_USER_ERROR);
				}
				userService.changePwd(jwtUser.getUsername(), oldPwd, newPwd);
				return R.success();
			}
			return R.result(ReturnCode.OPER_FAILTURE);
		} catch (Exception e) {
			return R.failure(e);
		}
	}

	@ApiOperation(value = "跳转页", hidden = true)
	@RequestMapping(value = "index", method = { RequestMethod.GET })
	public String index(Model model) {
		return "user/user-list";
	}
}
class UserVO  extends PaginationEntity {
	private String id;
	private String username;
	
	private String email;
	
	private boolean enabled;
	
	private String defaultRole;

	
	public UserVO() {
		super();
	}

	public UserVO(String id, String username, String email, boolean enabled, String defaultRole) {
		super();
		this.id=id;
		this.username = username;
		this.email = email;
		this.enabled = enabled;
		this.defaultRole = defaultRole;
	}

	public String getUsername() {
		return username;
	}

	public void setUsername(String username) {
		this.username = username;
	}

	public String getEmail() {
		return email;
	}

	public void setEmail(String email) {
		this.email = email;
	}

	public boolean isEnabled() {
		return enabled;
	}

	public void setEnabled(boolean enabled) {
		this.enabled = enabled;
	}

	public String getDefaultRole() {
		return defaultRole;
	}

	public void setDefaultRole(String defaultRole) {
		this.defaultRole = defaultRole;
	}

	public String getId() {
		return id;
	}

	public void setId(String id) {
		this.id = id;
	}
}
